package com.cskaoyan.shopping.service.impl;

import com.cskaoyan.mall.commons.exception.ExceptionProcessorUtils;
import com.cskaoyan.mall.constant.ShoppingRetCode;
import com.cskaoyan.mall.dto.ClearCartItemRequest;
import com.cskaoyan.mall.dto.ClearCartItemResponse;
import com.cskaoyan.shopping.converter.CartItemConverter;
import com.cskaoyan.shopping.dal.entitys.Item;
import com.cskaoyan.shopping.dal.persistence.CartProductDtoMapper;
import com.cskaoyan.shopping.dal.persistence.ItemMapper;
import com.cskaoyan.shopping.dto.*;
import com.cskaoyan.shopping.service.ICartService;
import lombok.extern.slf4j.Slf4j;
import org.redisson.api.RMap;
import org.redisson.api.RedissonClient;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.*;
import java.util.stream.Collectors;

/**
 * @auther zk
 * @date 2022/7/29 16:57
 */
@Slf4j
@Service
public class ICartServiceImpl implements ICartService {

    @Autowired
    ItemMapper itemMapper;
    @Autowired
    RedissonClient redissonClient;
    // @Autowired
    // CartProductDtoMapper cartProductDtoMapper;

    /*
     * @description:获得购物车列表
     * @author: zhang tao
     * @date: 2022-07-29 22:39
     * @param:
     * @return:
     **/

    @Override
    public CartListByIdResponse getCartListById(CartListByIdRequest request) {
        CartListByIdResponse response = new CartListByIdResponse();
        try {
            request.requestCheck();
            //根据用户id获取redis存的购物车数据
            RMap<String, Object> map = redissonClient.getMap(request.getUserId().toString());
            List<CartProductDto> productDtoList = new ArrayList<>();
            Set<Map.Entry<String, Object>> entries = map.entrySet();
            for (Map.Entry<String, Object> goods : entries) {
                CartProductDto goodsValue = (CartProductDto) goods.getValue();
                productDtoList.add(goodsValue);
            }
            response.setCode(ShoppingRetCode.SUCCESS.getCode());
            response.setMsg(ShoppingRetCode.SUCCESS.getMessage());
            response.setCartProductDtos(productDtoList);
        } catch (Exception e) {
            log.error("ICartServiceImpl.getCartListById occur Exception :" + e);
            ExceptionProcessorUtils.wrapperHandlerException(response, e);

        }
        return response;
    }

    /*
     * @description:添加购物车
     * @author: zhang tao
     * @date: 2022-07-29 22:40
     * @param:
     * @return:
     **/
    @Override
    public AddCartResponse addToCart(AddCartRequest request) {
        AddCartResponse response = new AddCartResponse();
        try {
            request.requestCheck();
            //获取redis键值对，将购物车信息存入redis
            RMap<String,CartProductDto> map = redissonClient.getMap(request.getUserId().toString());
            String itemId = request.getItemId().toString();
            CartProductDto cartProductDto =map.get(itemId);
            if (cartProductDto != null) {
                //购物车已有商品,商品数量加1
                cartProductDto.setProductNum(cartProductDto.getProductNum() + request.getNum());
            } else {
                //查询商品信息
                Item item = itemMapper.selectByPrimaryKey(itemId);
                cartProductDto = CartItemConverter.item2Dto(item);
                cartProductDto.setProductNum((long) request.getNum());
                cartProductDto.setChecked("true");
            }
            //数量超过限制，存入失败！
            if (cartProductDto.getProductNum() > cartProductDto.getLimitNum()) {
                response.setCode(ShoppingRetCode.OVER_LIMIT_NUM.getCode());
                response.setMsg(ShoppingRetCode.OVER_LIMIT_NUM.getMessage());
                return response;
            }
            //存入商品信息
            map.put(itemId, cartProductDto);
            //成功，即设置状态码信息
            response.setCode(ShoppingRetCode.SUCCESS.getCode());
            response.setMsg(ShoppingRetCode.SUCCESS.getMessage());
        } catch (Exception e) {
            log.error("ICartServiceImpl.addToCart occur Exception :" + e);
            ExceptionProcessorUtils.wrapperHandlerException(response, e);
        }

        return response;
    }

    @Override
    public UpdateCartResponse updateCart(UpdateCartRequest request) {

        UpdateCartResponse response = new UpdateCartResponse();
        try {
            request.requestCheck();

            String userId = request.getUserId().toString();
            String itemId = request.getItemId().toString();
            Long num = Long.valueOf(request.getNum());
            String checked = request.getChecked();

            Map<String, CartProductDto> map = redissonClient.getMap(userId);
            CartProductDto cartProduct = map.get(itemId);

            if (num > cartProduct.getLimitNum()) {
                response.setCode(ShoppingRetCode.OVER_LIMIT_NUM.getCode());
                response.setMsg(ShoppingRetCode.OVER_LIMIT_NUM.getMessage());
                return response;
            }

            cartProduct.setProductNum(num);
            cartProduct.setChecked(checked);
            map.put(itemId, cartProduct);

            response.setCode(ShoppingRetCode.SUCCESS.getCode());
            response.setMsg(ShoppingRetCode.SUCCESS.getMessage());
        } catch (Exception e) {
            log.error("ICartServiceImpl.updateCart occur Exception :" + e);
            ExceptionProcessorUtils.wrapperHandlerException(response, e);
        }
        return response;
    }

    @Override
    public CheckAllItemResponse checkAllCartItem(CheckAllItemRequest request) {
        CheckAllItemResponse response = new CheckAllItemResponse();
        try {
            request.requestCheck();

            String userId = request.getUserId().toString();
            String checked = request.getChecked();

            Map<String, CartProductDto> map = redissonClient.getMap(userId);
            map.forEach((key, value) -> {
                value.setChecked(checked);
                map.put(key, value);
            });

            response.setCode(ShoppingRetCode.SUCCESS.getCode());
            response.setMsg(ShoppingRetCode.SUCCESS.getMessage());
        } catch (Exception e) {
            log.error("ICartServiceImpl.updateCart occur Exception :" + e);
            ExceptionProcessorUtils.wrapperHandlerException(response, e);
        }
        return response;
    }

    @Override
    public DeleteCartItemResponse deleteCartItem(DeleteCartItemRequest request) {
        DeleteCartItemResponse response = new DeleteCartItemResponse();

        try {
            request.requestCheck();

            String userId = request.getUserId().toString();
            String itemId = request.getItemId().toString();
            Map<String, CartProductDto> map = redissonClient.getMap(userId);
            map.remove(itemId);
            response.setCode(ShoppingRetCode.SUCCESS.getCode());
            response.setMsg(ShoppingRetCode.SUCCESS.getMessage());
        } catch (Exception e) {
            log.error("ICartServiceImpl.deleteCartItem occur Exception :" + e);
            ExceptionProcessorUtils.wrapperHandlerException(response, e);
        }
        return response;
    }

    @Override
    public DeleteCheckedItemResposne deleteCheckedItem(DeleteCheckedItemRequest request) {
        DeleteCheckedItemResposne response = new DeleteCheckedItemResposne();
        try {
            request.requestCheck();

            String userId = request.getUserId().toString();
            Map<String, CartProductDto> map = redissonClient.getMap(userId);
            map.forEach((key, value) -> {
                if ("true".equals(value.getChecked())) {
                    map.remove(key);
                }
            });

            response.setCode(ShoppingRetCode.SUCCESS.getCode());
            response.setMsg(ShoppingRetCode.SUCCESS.getMessage());
        } catch (Exception e) {
            log.error("ICartServiceImpl.deleteCheckedItem occur Exception :" + e);
            ExceptionProcessorUtils.wrapperHandlerException(response, e);
        }
        return response;
    }

    @Override
    public ClearCartItemResponse clearCartItemByUserID(ClearCartItemRequest request) {
        Long userId = request.getUserId();
        List<Long> buyProductIds = request.getProductIds();

        String collect = buyProductIds.stream().map(String::valueOf).collect(Collectors.joining(","));
        System.out.println(collect);

        RMap<String, CartProductDto> map = redissonClient.getMap(userId.toString());

        map.forEach((key, value) -> {
            if ("true".equals(value.getChecked())) {
                map.remove(key);
            }
        });
        return null;
    }
}
